package data.complex;

import data.base.Vector3;
import data.base.Vertex;
import data.hierarchy.IVertexProvider;

public class Boundary extends Vector3{
  private Vector3 minorBounds;
  private Vector3 majorBounds;
  private Vector3 dimension;
  private int vertexCount = 0;
  
  public Boundary(double minX, double minY, double minZ, double majX, double majY, double majZ){
    super(0, 0, 0);
    minorBounds = new Vector3(minX, minY, minZ);
    majorBounds = new Vector3(majX, majY, majZ);
    initPosition();
  }
  
  public Boundary(IVertexProvider points){
    super(0, 0, 0);
    initialize(points);
  }
  
  private void initialize(IVertexProvider points){
    double minX = 0, minY = 0, minZ = 0;
    double majX = 0, majY = 0, majZ = 0;
        
    for(Vertex v : points.getVertices()){
      
      if(vertexCount == 0){        
        minX = v.getX();
        majX = minX;
        
        minY = v.getY();
        majY = minY;
        
        minZ = v.getZ();
        majZ = minZ;
      }
      
      if(v.getX() < minX) minX = v.getX();
      else if(v.getX() > majX) majX = v.getX();
      
      if(v.getY() < minY) minY = v.getY();
      else if(v.getY() > majY) majY = v.getY();
      
      if(v.getZ() < minZ) minZ = v.getZ();
      else if(v.getZ() > majZ) majZ = v.getZ();
      
      vertexCount++;
    }
    minorBounds = new Vector3(minX, minY, minZ);
    majorBounds = new Vector3(majX, majY, majZ);
    
    initPosition();
  }
  
  private void initPosition(){
    add(minorBounds);
    add(majorBounds);
    multiplicate(0.5);
  }

  public Vector3 getMinorBounds() {
    return minorBounds;
  }

  public Vector3 getMajorBounds() {
    return majorBounds;
  }
  
  public Vector3 getDimension(){
    if(dimension == null){
      dimension = new Vector3(getMinorBounds(), getMajorBounds());
    }
    return dimension;
  }
  
  public int getVertexCount(){
    return vertexCount;
  }
  
  public Boundary getexpandedBoundary(double addition){
    return new Boundary(
        minorBounds.getX() - addition, 
        minorBounds.getY() - addition, 
        minorBounds.getZ() - addition,
        majorBounds.getX() + addition, 
        majorBounds.getY() + addition, 
        majorBounds.getZ() + addition);
  }
}
